#!/usr/bin/env python
#
# Copyright 2007 Google Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
import os
import gdata.gauth
import gdata.apps.groups
import gdata.apps.groups.service
import gdata.contacts
import gdata.contacts.service

from google.appengine.ext.webapp import template
from google.appengine.ext import db
from google.appengine.ext import webapp
from google.appengine.ext.webapp import util
from google.appengine.api import users
from django.utils import simplejson as JSON
import logging
import urllib
import datetime

API_KEY = 'ABQIAAAAZYOEu5SF09ohR_uh4BAcsBRA-GiCq161ZX1F4jFizGPQBb4vCBT_8Nz_Br3BoiozdiMSCLd3UsOztA'
SITE = ''
CONSUMER_KEY = 'groups-webui.appspot.com'
CONSUMER_SECRET='2QVVqm2mFzk3ta5RAC6iZzSp'

class FeedCache(db.Model):
    feed = db.StringProperty(required=True)
    cache = db.TextProperty(required=True)
    expiry = db.DateTimeProperty()

class MainHandler(webapp.RequestHandler):
    def get_feed_as_json(self, handler,params):
        return handler(*params)

    def clear_old_data(self):
        rows = db.GqlQuery("SELECT * FROM FeedCache WHERE expiry < :1",
                           datetime.datetime.now())
        count = 0;
        for row in rows:
            count += 1
            row.delete()
            
        if count > 0:
            logging.info("Cleared %d rows from cache." % count )


    def fetch_feed(self,handler,force_feed,params=[]):
        row = None
        feed = "%s:%s:%s" % (SITE,handler.__name__ , str(params))
        if not force_feed:
            row = db.GqlQuery("SELECT * FROM FeedCache WHERE feed=:1 and expiry > :2",
                              feed,
                              datetime.datetime.now()).get()
        if row is not None:
            return eval(row.cache)
        else:
            rows = db.GqlQuery("SELECT * FROM FeedCache WHERE feed=:1",
                              feed)
            for row in rows:
                row.delete()

            data = self.get_feed_as_json(handler,params)
            data = { 'feed': feed,
                     'expiry': str(datetime.datetime.now() + datetime.timedelta(hours=1)),
                     'data': data,
                     }
            entity = FeedCache(feed=feed,
                               cache=str(data),
                               expiry=datetime.datetime.now() + datetime.timedelta(hours=1))
            entity.put()
            self.clear_old_data()
            return data

    @staticmethod
    def login():
        service = gdata.apps.groups.service.GroupsService(domain=SITE)
        service.SetOAuthInputParameters(gdata.auth.OAuthSignatureMethod.HMAC_SHA1,
                                        CONSUMER_KEY,
                                        consumer_secret=CONSUMER_SECRET,
                                        two_legged_oauth=True)
        return service

    def get(self, site):
        global SITE
        SITE = site

        # user = users.get_current_user()
        #        if not user or not user.email().endswith("@%s" % SITE ):
        #            self.redirect(users.create_login_url("/%s"% SITE))
        #            return
        if not SITE or not 'parent' in self.request.params or SITE not in self.request.params['parent']:
            self.redirect("http://google.com")
        service = MainHandler.login()
        force_feed = 'force' in self.request.params
        data = self.fetch_feed(service.RetrieveAllGroups, force_feed )

        groups = data['data']
        even = True;
        for i in groups:
            even = not(even)
            i['even'] = even
        path = os.path.join(os.path.dirname(__file__), 'groups.html')
        
        self.response.out.write(template.render(path,{'groups':groups,
                                                      'API_KEY':API_KEY, 
                                                      'groupsJSON': JSON.dumps(groups),
                                                      'SITE': SITE,
                                                      }))

class GadgetHandler(MainHandler):
    def get(self, site):
        global SITE
        SITE = site

        logging.info(SITE)

        if not SITE or not 'parent' in self.request.arguments() or SITE not in self.request.get('parent'):
            self.redirect("http://google.com")

        service = MainHandler.login()
        force_feed = 'force' in self.request.params
        data = self.fetch_feed(service.RetrieveAllGroups, force_feed )

        groups = data['data']
        even = True;
        for i in groups:
            even = not(even)
            i['even'] = even
        path = os.path.join(os.path.dirname(__file__), 'groups-gadget.html')
        
        self.response.out.write(template.render(path,{'groups':groups,
                                                      'API_KEY':API_KEY, 
                                                      'groupsJSON': JSON.dumps(groups),
                                                      'SITE': SITE,
                                                      }))


class UserHandler(MainHandler):
    def get(self, site, group):
        global SITE
        SITE = site

        service = MainHandler.login()
        force_feed = 'force' in self.request.params
    
        data = self.fetch_feed(service.RetrieveAllMembers,
                               force_feed, params=[group])
        members = data
        data = self.fetch_feed(service.RetrieveAllOwners,
                               force_feed, params=[group])
        owners = data

        data = { 'groupName': urllib.unquote(group),
                 'owners': owners,
                 'members': members }
        self.response.headers['content-type'] = 'application/json'
        self.response.headers.add_header('X-JSON', str(data))
        self.response.out.write(JSON.dumps(data))

def main():
    application = webapp.WSGIApplication([
            (r'^/(.*?)/users/(.*?)/?', UserHandler),
            (r'^/(.*?)/gadget', GadgetHandler),
            (r'^/(.*?)/?', MainHandler),
            ],
                                         debug=True)
    util.run_wsgi_app(application)


if __name__ == '__main__':
    main()
